package org.example.config;


import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;

//@Aspect
//@Component
@Slf4j
public class TongjiTimeAspect {

    private static ThreadLocal<Long> TIME = new ThreadLocal<>();

    //表示controller包下所有以select开头的类
    // 这就是一组切点：用来配置一组切点规则，用于匹配要横切的业务方法
    @Pointcut("execution(* org.example.controller.*.select*(..))")
    public void tongji(){}

    //写通知：包含切点是哪个？包含横切代码，包含通知(业务方法什么时候执行业务代码)
    @Before("tongji()")//业务方法执行前调用横切代码
    public void before(){
        //重点关注执行的统一杭茄代码
        log.debug("before");
        TIME.set(System.currentTimeMillis());//保存当前时间：开始时间
    }

    @After("tongji()")
    public void after(){
        log.debug("after");
        long start = TIME.get();
        long end = System.currentTimeMillis();
        log.debug("方法执行时间:{}",end - start);
    }

    @AfterReturning("tongji()")//在方法调用return 前执行
    public void afterReturning(){
        log.debug("after returning");
    }

    @AfterThrowing("tongji()")//在方法抛异常前执行
    public void afterThrowing(){
        log.debug("after throwing");
    }

    @Around("tongji()")//环绕通知：业务方法前后加入一些代码
    public Object around(ProceedingJoinPoint joinPoint){
        log.debug("around before");
        try {
            Object o =  joinPoint.proceed();
            log.debug("around after");
            return o;
        } catch (Throwable e) {
//            log.error("around执行业务方法出错！");
            throw new RuntimeException("around执行业务方法出错",e);
        }
    }
}
